
#define INVERSE_4PI 0.07957747154594766788444188168626
const vec3 cEye=vec3(0,0,0);

struct Light {
    vec3 pos;
    vec4 color;    
};

uniform Lights {
    Light lights[MAX_LIGHTS];
} GlobalLights;

vec3 Lighting(in vec3 normal, in vec3 location, in vec4 mat)
{
    vec3 outColor=vec3(0,0,0);
    vec3 view=normalize(cEye-location);
    for(int i=0; i<MAX_LIGHTS; i++)
        if(GlobalLights.lights[i].color.a > 0) {
            vec3 incoming=location-GlobalLights.lights[i].pos;
            float aten=inversesqrt(dot(incoming,incoming));
            incoming*=aten;
            aten*=aten*INVERSE_4PI*GlobalLights.lights[i].color.a;
            outColor-=min(0, dot(incoming, normal))*GlobalLights.lights[i].color.rgb*aten*mat.rgb;
            // Obtain <N,H>
            vec3 reflected=reflect(incoming, normal);
            float spec=(dot(reflected, view)+1)*0.5;
            float smoothness=1/(mat.a*mat.a);
            spec=1/spec;
            // compute the coefficient
            spec=exp((1-spec)*smoothness)*smoothness*spec*spec*INVERSE_4PI*4;
            // nullify in case of backface
            spec*=(sign(dot(reflected,normal))+1)*0.5;
            outColor+=spec*GlobalLights.lights[i].color.rgb*aten;
        }
    return outColor;
}
